package drds.plus.executor.function.scalar.filter;

import drds.plus.executor.ExecuteContext;
import drds.plus.sql_process.type.Type;
import drds.tools.$;
import lombok.extern.slf4j.Slf4j;

import java.util.Collection;
import java.util.List;

@Slf4j
public class In extends Filter {

    protected Boolean computeInner(ExecuteContext executeContext, Object[] args) {
        Type type = this.getArgType();

        Object left = args[0];
        Object right = args[1];

        if (right instanceof List) {
            if ($.isNotNullAndHasElement((Collection) right)) {
                if (((List) right).get(0) instanceof List) {
                    right = ((List) right).get(0);
                }
            }
            for (Object eachRight : (List) right) {
                // 是否出现(id,columnName) in ((1,'a'),(2,'b'))
                if (left instanceof RowValueList) {
                    if (!(eachRight instanceof RowValueList)) {
                        throw new UnsupportedOperationException("impossible");
                    }

                    List<Object> leftArgs = ((RowValueList) left).getValueList();
                    List<Object> rightArgs = ((RowValueList) eachRight).getValueList();
                    if (leftArgs.size() != rightArgs.size()) {
                        throw new UnsupportedOperationException("impossible");
                    }

                    boolean notMatch = false;
                    for (int i = 0; i < leftArgs.size(); i++) {
                        Object leftArg = leftArgs.get(i);
                        Object rightArg = rightArgs.get(i);

                        if (getType(leftArg).compare(leftArg, rightArg) != 0) {
                            // 不匹配
                            notMatch = true;
                            break;
                        }
                    }

                    if (!notMatch) {
                        return true;
                    }
                } else {
                    if (type.compare(left, eachRight) == 0) {
                        return true;
                    }
                }
            }
        }

        return false;
    }

    public String[] getFunctionNames() {
        return new String[]{"in"};
    }
}
